﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Collections;
using System.Resources;
using System.Globalization;

namespace JCard
{
    public partial class fLearnVoc : Form    
    {
        #region Variables for resource
        ResourceManager objResourceManager;
        CultureInfo objCulInfo;
        #endregion

        #region variables
        // Parent form used when back to Parent form
        fCLesson frmParent;
        ArrayList arrVocs;
        ArrayList arrVocsWrong;
        ArrayList arrVocsRight;
        DTO_VOC curDtoVoc = null;
        int incorrect = 0;
        int correct = 0;
        int total = 0;
        string dbPath;
        int isLearnType;

        DTO_Setting dtoSetting = new DTO_Setting();
        BUS_JCARD buJcard;
        #endregion

        #region constructors
        public fLearnVoc(string topicName, ArrayList arrVocs, int isLearnType, fCLesson frmParent, string dbPath)
        {
            this.frmParent = frmParent;
            this.dbPath = dbPath;
            this.arrVocs = arrVocs;
            this.arrVocsRight = new ArrayList();
            this.arrVocsWrong = new ArrayList();
            this.isLearnType = isLearnType;
            buJcard = new BUS_JCARD(dbPath);

            InitializeComponent();

            this.lblTitle.Text = topicName;

            SetDisplayLabel();
        }

        private void SetDisplayLabel()
        {
            objResourceManager = new ResourceManager("JCard.Resources", typeof(fCLesson).Assembly);
            objCulInfo = new CultureInfo(Common.GetConfigValue(Constants.CONFIG_LANGUAGE_KEY, Constants.CONFIG_LANGUAGE_VALUE));
        }
        #endregion

        #region Loading & Display
        private void fLearnVoc_Load(object sender, EventArgs e)
        {
            total = this.arrVocs.Count;
            incorrect = 0;
            correct = 0;

            SetSettingValue();
            SetHeight();            

            btnAnswer.Enabled = true;
            btnNext.Enabled = false;
            lblEdit.Enabled = false;
            lblStatus.Visible = false;
            lblHiraganaAnswer.Visible = true;
            lblMeaningAnswer.Visible = true;

            GetRandomVoc();
            DisplayCurVoc(false);

            DisplayStatus();
        }

        private void SetSettingValue()
        {
            // Read config
            string startupPath = Application.StartupPath;
            startupPath += @"\Setting.ini";
            dtoSetting = new DTO_Setting();
            dtoSetting = ReadIniSetting(startupPath);

            //           
            //Set config 
            //
            switch (isLearnType)
            {
                case 1:
                    // Kanji
                    pnlKanji.BackColor = Color.FromArgb(dtoSetting.Kanji_BackColor);
                    pnlKanji.ForeColor = Color.FromArgb(dtoSetting.Kanji_FontColor);
                    lblQuestion.Font = Common.ChangeFontSize(lblQuestion.Font, dtoSetting.Kanji_Fontsize);

                    //Hiragana
                    pnlHiragana.BackColor = Color.FromArgb(dtoSetting.Hiragana_BackColor);
                    pnlHiragana.ForeColor = Color.FromArgb(dtoSetting.Hiragana_FontColor);
                    txtHiragana.Font = Common.ChangeFontSize(txtHiragana.Font, dtoSetting.Hiragana_Fontsize);

                    //Meaning
                    pnlMeaning.BackColor = Color.FromArgb(dtoSetting.Meaning_BackColor);
                    pnlMeaning.ForeColor = Color.FromArgb(dtoSetting.Meaning_FontColor);
                    txtMeaningKanji.Font = Common.ChangeFontSize(txtMeaningKanji.Font, dtoSetting.Meaning_Fontsize);
                    break;
                case 2:
                    // Kanji
                    pnlKanji.BackColor = Color.FromArgb(dtoSetting.Kanji_BackColor);
                    pnlKanji.ForeColor = Color.FromArgb(dtoSetting.Kanji_FontColor);
                    lblQuestion.Font = Common.ChangeFontSize(lblQuestion.Font, dtoSetting.Kanji_Fontsize);

                    //Hiragana
                    pnlHiragana.BackColor = Color.FromArgb(dtoSetting.Hiragana_BackColor);
                    pnlHiragana.ForeColor = Color.FromArgb(dtoSetting.Hiragana_FontColor);
                    txtHiragana.Font = Common.ChangeFontSize(txtHiragana.Font, dtoSetting.Hiragana_Fontsize);
                    break;
                case 3:
                    //Kanji
                    pnlKanji.BackColor = Color.FromArgb(dtoSetting.Meaning_BackColor);
                    pnlKanji.ForeColor = Color.FromArgb(dtoSetting.Meaning_FontColor);
                    lblQuestion.Font = Common.ChangeFontSize(lblQuestion.Font, dtoSetting.Meaning_Fontsize);

                    //Meaning
                    pnlMeaning.BackColor = Color.FromArgb(dtoSetting.Kanji_BackColor);
                    pnlMeaning.ForeColor = Color.FromArgb(dtoSetting.Kanji_FontColor);
                    txtMeaningKanji.Font = Common.ChangeFontSize(txtMeaningKanji.Font, dtoSetting.Kanji_Fontsize);                    
                    break;
            }
        }

        private void SetHeight()
        {
            int kanjiHeight = 0, hiraHeight = 0, meanHeight = 0;

            kanjiHeight = (int)Common.GetSizeOfText(lblQuestion, lblQuestion.Text, lblQuestion.Font).Height + 4 * Constants.TOP_BOTTOM_SPACE_LABEL_PANEL;

            if (isLearnType == 1 || isLearnType == 2)
                hiraHeight = txtHiragana.Height + lblHiraganaAnswer.Height + 2 * Constants.TOP_BOTTOM_SPACE_LABEL_PANEL;

            if (isLearnType == 1 || isLearnType == 3)
                meanHeight = txtMeaningKanji.Height + lblMeaningAnswer.Height + 2 * Constants.TOP_BOTTOM_SPACE_LABEL_PANEL;

            int totalHeight = kanjiHeight + hiraHeight + meanHeight + pnlCard.Padding.Top + pnlCard.Padding.Bottom;
     
            this.MinimumSize = new Size(this.Width, this.Height - pnlCard.Height + totalHeight);
            this.Height = this.Height - pnlCard.Height + totalHeight;
            this.MaximumSize = new Size(2*Constants.MAX_WIDTH, this.Height);            

            pnlCard.Height = totalHeight;

            switch (isLearnType)
            {
                case 1:
                    pnlHiragana.Visible = true;
                    pnlMeaning.Visible = true;
                    pnlStatusBot.Height = pnlButtons.Height;
                    pnlHiragana.Height = hiraHeight;
                    pnlBorderCard.Height = kanjiHeight + hiraHeight + meanHeight;
                    pnlMeaning.Height = meanHeight;
                    break;
                case 2:                    
                    pnlHiragana.Visible = true;
                    pnlMeaning.Visible = false;
                    pnlStatusBot.Height = 0;
                    pnlMeaning.Height = 0;
                    pnlBorderCard.Height = kanjiHeight + hiraHeight;
                    pnlHiragana.Height = hiraHeight;
                    break;
                case 3:
                    pnlHiragana.Visible = false;
                    pnlMeaning.Visible = true;
                    pnlStatusBot.Height = 0;
                    pnlHiragana.Height = 0;
                    pnlBorderCard.Height = kanjiHeight + meanHeight;
                    pnlMeaning.Height = meanHeight;
                    break;
            }            
        }

        private DTO_Setting ReadIniSetting(string filePath)
        {
            BUS_Setting busSetting = new BUS_Setting();
            DTO_Setting dtoSetting = new DTO_Setting();
            dtoSetting = busSetting.ReadSetting(filePath);
            return dtoSetting;
        }

        private void GetRandomVoc()
        {
            Random rd = new Random();
            int curIndex = rd.Next(0, arrVocs.Count - 1);
            curDtoVoc = (DTO_VOC)arrVocs[curIndex];

            arrVocs.RemoveAt(curIndex);
        }

        private void DisplayCurVoc(bool isShowAnswer)
        {
            switch (isLearnType)
            {
                case 1:
                    lblQuestion.Text = curDtoVoc.Kanji;

                    if (isShowAnswer)
                    {
                        lblHiraganaAnswer.Text = curDtoVoc.Hiragana;
                    }
                    else
                    {
                        lblHiraganaAnswer.Text = string.Empty;
                    }

                    txtHiragana.Clear();
                    txtHiragana.ReadOnly = false;

                    if (isShowAnswer)
                    {
                        lblMeaningAnswer.Text = curDtoVoc.Meaning;
                    }
                    else
                    {
                        lblMeaningAnswer.Text = string.Empty;
                    }

                    txtMeaningKanji.Clear();
                    txtMeaningKanji.ReadOnly = false;

                    txtHiragana.Focus();
                    break;
                case 2:
                    lblQuestion.Text = curDtoVoc.Kanji;

                    if (isShowAnswer)
                    {
                        lblHiraganaAnswer.Text = curDtoVoc.Hiragana;
                    }
                    else
                    {
                        lblHiraganaAnswer.Text = string.Empty;
                    }

                    txtHiragana.Clear();
                    txtHiragana.ReadOnly = false;

                    txtHiragana.Focus();
                    break;
                case 3:
                    lblQuestion.Text = curDtoVoc.Meaning;
                    if (isShowAnswer)
                    {
                        lblMeaningAnswer.Text = curDtoVoc.Kanji;
                    }
                    else
                    {
                        lblMeaningAnswer.Text = string.Empty;
                    }

                    txtMeaningKanji.Clear();
                    txtMeaningKanji.ReadOnly = false;
                    txtMeaningKanji.Focus();
                    break;
            }
        }

        private void DisplayStatus()
        {
            lblRemaining.Text = (total - incorrect - correct).ToString();
            lblCorrect.Text = correct.ToString();
            lblIncorrect.Text = incorrect.ToString();
        }
        #endregion

        private void btnAnswer_Click(object sender, EventArgs e)
        {
            lblStatus.Visible = true;

            switch (isLearnType)
            {
                case 1:
                    lblHiraganaAnswer.Text = curDtoVoc.Hiragana;
                    lblMeaningAnswer.Text = curDtoVoc.Meaning;

                    if (Common.CompareText(txtHiragana.Text, lblHiraganaAnswer.Text) &&
                        Common.CompareText(txtMeaningKanji.Text, lblMeaningAnswer.Text))
                    {
                        correct++;

                        // Update kanji answered status
                        curDtoVoc.KanjiAnswered++;
                        buJcard.UpdateVocabularyStatus(curDtoVoc);

                        lblStatus.ForeColor = Color.Blue;
                        lblStatus.Text = Constants.RES_LEARN_CORRECT_VALUE;
                        arrVocsRight.Add(new DTO_VOC(curDtoVoc));
                        txtHiragana.ReadOnly = true;
                        txtMeaningKanji.ReadOnly = true;
                        btnNext.Enabled = true;
                        btnAnswer.Enabled = false;
                        btnNext.Focus();
                    }
                    else
                    {
                        incorrect++;

                        // Update kanji missed status
                        curDtoVoc.KanjiMissed++;
                        buJcard.UpdateVocabularyStatus(curDtoVoc);

                        lblStatus.ForeColor = Color.Red;
                        lblStatus.Text = Constants.RES_LEARN_INCORRECT_VALUE;
                        arrVocsWrong.Add(new DTO_VOC(curDtoVoc));
                        if (Common.CompareText(txtHiragana.Text, lblHiraganaAnswer.Text))
                            txtHiragana.ReadOnly = true;
                        else
                            txtHiragana.ForeColor = Color.Red;

                        if (Common.CompareText(txtMeaningKanji.Text, lblMeaningAnswer.Text))
                            txtMeaningKanji.ReadOnly = true;
                        else
                            txtMeaningKanji.ForeColor = Color.Red;

                        btnAnswer.Enabled = false;
                        btnNext.Enabled = false;

                        if (!txtHiragana.ReadOnly) txtHiragana.Focus();
                        else txtMeaningKanji.Focus();
                    }
                    break;
                case 2:
                    lblHiraganaAnswer.Text = curDtoVoc.Hiragana;
                    lblQuestion.Text += "（" + curDtoVoc.Meaning + "）";

                    if (Common.CompareText(txtHiragana.Text, curDtoVoc.Hiragana))
                    {
                        correct++;

                        // Update kanji answered status
                        curDtoVoc.KanjiAnswered++;
                        buJcard.UpdateVocabularyStatus(curDtoVoc);

                        lblStatus.ForeColor = Color.Blue;
                        lblStatus.Text = Constants.RES_LEARN_CORRECT_VALUE;
                        arrVocsRight.Add(new DTO_VOC(curDtoVoc));
                        txtHiragana.ReadOnly = true;
                        btnNext.Enabled = true;
                        btnAnswer.Enabled = false;
                        btnNext.Focus();
                    }
                    else
                    {
                        incorrect++;

                        // Update kanji missed status
                        curDtoVoc.KanjiMissed++;
                        buJcard.UpdateVocabularyStatus(curDtoVoc);

                        lblStatus.ForeColor = Color.Red;
                        lblStatus.Text = Constants.RES_LEARN_INCORRECT_VALUE;
                        arrVocsWrong.Add(new DTO_VOC(curDtoVoc));
                        txtHiragana.ForeColor = Color.Red;
                        btnAnswer.Enabled = false;
                        btnNext.Enabled = false;
                        txtHiragana.Focus();
                    }
                    break;
                case 3:
                    lblMeaningAnswer.Text = curDtoVoc.Kanji;                    

                    if (Common.CompareText(txtMeaningKanji.Text, lblMeaningAnswer.Text))
                    {
                        correct++;

                        // Update meaning answered status
                        curDtoVoc.MeaningAnswered++;
                        buJcard.UpdateVocabularyStatus(curDtoVoc);

                        lblStatus.ForeColor = Color.Blue;
                        lblStatus.Text = Constants.RES_LEARN_CORRECT_VALUE;
                        arrVocsRight.Add(new DTO_VOC(curDtoVoc));
                        txtMeaningKanji.ReadOnly = true;
                        btnNext.Enabled = true;
                        btnAnswer.Enabled = false;
                        btnNext.Focus();
                    }
                    else
                    {
                        lblQuestion.Text += "（" + curDtoVoc.Hiragana + "）";

                        incorrect++;

                        // Update meaning missed status
                        curDtoVoc.MeaningMissed++;
                        buJcard.UpdateVocabularyStatus(curDtoVoc);

                        lblStatus.ForeColor = Color.Red;
                        lblStatus.Text = Constants.RES_LEARN_INCORRECT_VALUE;
                        arrVocsWrong.Add(new DTO_VOC(curDtoVoc));
                        txtMeaningKanji.ForeColor = Color.Red;
                        btnNext.Enabled = false;
                        btnAnswer.Enabled = false;
                        txtMeaningKanji.Focus();
                    }
                    break;
            }

            DisplayStatus();
            lblEdit.Enabled = true;
        }

        private void btnNext_Click(object sender, EventArgs e)
        {
            lblStatus.Visible = false;
            lblEdit.Enabled = false;

            if (arrVocs.Count > 0)
            {
                btnAnswer.Enabled = true;
                btnNext.Enabled = false;

                GetRandomVoc();
                DisplayCurVoc(false);                
            }
            else
            {
                if (incorrect > 0)
                {
                    if (Common.ShowConfirmMsg(objCulInfo, objResourceManager,
                            Constants.RES_NOT_FINISH_LEARN_VOC_NAME, Constants.RES_NOT_FINISH_LEARN_VOC_VALUE,
                            correct, incorrect, incorrect) == DialogResult.Yes)
                    {
                        arrVocs.AddRange(arrVocsWrong.ToArray());
                        arrVocsWrong.Clear();

                        incorrect = 0;

                        btnAnswer.Enabled = true;
                        btnNext.Enabled = false;
                        GetRandomVoc();
                        DisplayCurVoc(false);
                        DisplayStatus();
                    }
                    else
                    {
                        this.Close();
                    }
                }
                else
                {
                    if (Common.ShowConfirmMsg(objCulInfo, objResourceManager,
                            Constants.RES_FINISH_LEARN_VOC_NAME, Constants.RES_FINISH_LEARN_VOC_VALUE) == DialogResult.Yes)
                    {
                        arrVocs.AddRange(arrVocsRight.ToArray());
                        arrVocsRight.Clear();

                        incorrect = 0;
                        correct = 0;

                        btnAnswer.Enabled = true;
                        btnNext.Enabled = false;

                        GetRandomVoc();
                        DisplayCurVoc(false);
                        DisplayStatus();
                    }
                    else
                    {
                        this.Close();
                    }
                }
            }
        }

        private void lblEdit_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            fEditVoc editVoc = new fEditVoc(curDtoVoc, dbPath);
            if (editVoc.ShowDialog() == DialogResult.OK)
            {
                curDtoVoc = editVoc.UpdateDtoVoc;

                if (lblStatus.Visible && lblStatus.Text.Equals(Constants.RES_LEARN_CORRECT_VALUE))
                {
                    arrVocsRight[arrVocsRight.Count - 1] = curDtoVoc;
                }
                else if (lblStatus.Visible && lblStatus.Text.Equals(Constants.RES_LEARN_INCORRECT_VALUE))
                {
                    arrVocsWrong[arrVocsWrong.Count - 1] = curDtoVoc;
                }

                DisplayCurVoc(true);
            }
        }

        private void txtHiragana_TextChanged(object sender, EventArgs e)
        {
            if (!btnAnswer.Enabled)
            {
                if (Common.CompareText(txtHiragana.Text, lblHiraganaAnswer.Text))
                {
                    txtHiragana.ForeColor = Color.Black;
                    txtHiragana.ReadOnly = true;

                    if (isLearnType != 1)
                    {
                        btnNext.Enabled = true;
                        btnNext.Focus();
                    }
                    else
                    {
                        if (txtMeaningKanji.ReadOnly)
                        {
                            btnNext.Enabled = true;
                            btnNext.Focus();
                        }
                        else
                        {
                            txtMeaningKanji.Focus();
                        }
                    }
                }
            }
        }

        private void txtMeaningKanji_TextChanged(object sender, EventArgs e)
        {
            if (!btnAnswer.Enabled)
            {
                if (Common.CompareText(txtMeaningKanji.Text, lblMeaningAnswer.Text))
                {
                    txtMeaningKanji.ForeColor = Color.Black;
                    txtMeaningKanji.ReadOnly = true;

                    if (isLearnType != 1)
                    {
                        btnNext.Enabled = true;
                        btnNext.Focus();
                    }
                    else
                    {
                        if (txtHiragana.ReadOnly)
                        {
                            btnNext.Enabled = true;
                            btnNext.Focus();
                        }
                        else
                        {
                            txtHiragana.Focus();
                        }
                    }
                }
            }
        }

        private void fLearnVoc_FormClosed(object sender, FormClosedEventArgs e)
        {
            frmParent.ReShow();
        }

        private void txtHiragana_Enter(object sender, EventArgs e)
        {
            txtHiragana.ImeMode = System.Windows.Forms.ImeMode.Hiragana;
        }

        private void txtMeaningKanji_Enter(object sender, EventArgs e)
        {            
            if (isLearnType == 1)
            {
                txtMeaningKanji.ImeMode = ImeMode.Alpha;
            }
            else
            {
                txtMeaningKanji.ImeMode = System.Windows.Forms.ImeMode.Hiragana;
            }
        }                
       }
}
